import sys
import random
import matplotlib.pyplot as plt
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
from PyQt5.QtWidgets import QApplication, QWidget, QPushButton, QVBoxLayout, QLabel
from PyQt5.QtCore import QTimer

class MainWindow(QWidget):
    def __init__(self):
        super().__init__()

        self.initUI()

    def initUI(self):
        self.setGeometry(100, 100, 600, 400)
        self.setWindowTitle('Bubble Sort Visualization')

        # 创建按钮
        self.button = QPushButton('Start Bubble Sort', self)
        self.button.clicked.connect(self.startBubbleSort)

        # 创建标签用于显示动画
        self.label = QLabel(self)
        self.label.setStyleSheet('background-color: lightGray;')

        # 创建垂直布局，并将按钮和标签添加到布局中
        layout = QVBoxLayout()
        layout.addWidget(self.button)
        layout.addWidget(self.label)

        self.setLayout(layout)

        # 初始化 matplotlib 图形显示
        self.fig, self.ax = plt.subplots()
        self.canvas = FigureCanvas(self.fig)
        layout.addWidget(self.canvas)

    def startBubbleSort(self):
        self.data = random.sample(range(1, 20), 10)  # 生成随机样例数据
        self.currentIndex = 0

        # 创建定时器，每隔一段时间更新一次标签显示
        self.timer = QTimer(self)
        self.timer.timeout.connect(self.updateLabel)
        self.timer.start(500)  # 每500毫秒更新一次

    def updateLabel(self):
        if self.currentIndex < len(self.data) - 1:
            # 执行一步冒泡排序
            if self.data[self.currentIndex] > self.data[self.currentIndex + 1]:
                # 交换元素
                self.data[self.currentIndex], self.data[self.currentIndex + 1] = \
                    self.data[self.currentIndex + 1], self.data[self.currentIndex]

            self.currentIndex += 1

            # 更新标签显示
            self.updateBarChart()
        else:
            # 排序完成，停止定时器
            self.timer.stop()

    def updateBarChart(self):
        self.ax.clear()
        colors = ['blue'] * len(self.data)  # 默认颜色为蓝色
        colors[self.currentIndex] = 'red'  # 当前正在比较的两个柱子设置为红色
        if self.currentIndex > 0:
            colors[self.currentIndex - 1] = 'red'

        self.ax.bar(range(len(self.data)), self.data, color=colors)
        self.ax.set_title('Bubble Sort')
        self.ax.set_xlabel('Index')
        self.ax.set_ylabel('Value')
        self.canvas.draw()

if __name__ == '__main__':
    app = QApplication(sys.argv)
    mainWindow = MainWindow()
    mainWindow.show()
    sys.exit(app.exec_())
